import { Injectable, HttpException, HttpStatus } from '@nestjs/common';
import { InjectRepository } from '@nestjs/typeorm';
import { UserEntity } from '@entities/user.entity';
import { Repository } from 'typeorm';
import { ExcludeDefault, FullAttr, ParticalSome } from '@type/type-helper';
import { stringify, v4 } from 'uuid';
import { encryptPassword } from '@utils/cryptogram';
import { configure } from 'configure/configure.module';
import { ErrorCode } from '@type/error-code';
import { JwtService } from '@nestjs/jwt';

@Injectable()
export class UserService {
    // userEnty: any
    constructor(
        @InjectRepository(UserEntity) private readonly userEnty: Repository<UserEntity>,
        private readonly jwtService: JwtService,
    ) {

    }
    /**
     * 
     * @param userId {UUID}
     */
    public async findOneById(userId: string) {
        return this.userEnty.findOne({where: {id: userId}});
    }
    /**
     * 
     * @param username
     */
    public async findOneByUsername(username: string) {
        return this.userEnty.findOne({where: {username: username}});
    }
    public async userExist(user: Partial<{id: string, username: string, phone: string, personId: string}>) {
        if(Object.keys(user).length === 0) {
            throw new HttpException({data: null, code: ErrorCode.FORM_ERROR}, HttpStatus.INTERNAL_SERVER_ERROR);
        } 
    }
    /**
     * 
     * @param user 
     * @description 注册用户
     */
    public async register(user: ParticalSome<ExcludeDefault<UserEntity, 'id'>, 'phone'|'avator'>): Promise<['exist'|null, Promise<UserEntity>]> {
        let existUser = await this.findOneByUsername(user.username);
        if(existUser != null) {
            return ['exist', null];
        }
        let userEnty = new UserEntity();
        userEnty.id = v4();
        userEnty.avator = user.avator;
        userEnty.username = user.username;
        userEnty.password = encryptPassword(user.password, configure.passwordSalt);
        // userEnty.gender = user.gender;
        userEnty.nickname = user.nickname;
        return this.userEnty.save(userEnty)
            .then(res => {
                console.log(res);
                return [null, res];
            })
            .catch(err => {
                return err
            });
    }

        /**
     * 
     * @param userId 
     * @description 删除用户
     */
    public async remove(userId:string): Promise<['exist'|null, boolean]> {
        let ressult = await this.userEnty.update(this.userEnty.create({id: userId}),{avator: ''});
        return [null, true];
    }
    /**
     * @description 验证是否登陆正确
     * @param account {账号可以为用户名或者手机号}
     * @param password 
     */
    public async validateUser(account: string, password: string): Promise<['NOT_EXIST'|'PASSWORD_ERR'|'SUCCESS', UserEntity]> {
        let result = await this.userEnty.findOne({where: [{username: account}, {phone: account}]});
        if(result == null) {
            return ['NOT_EXIST', null];
        }
        let passwd = encryptPassword(password, configure.passwordSalt);
        if(result.password !== passwd) {
            return ['PASSWORD_ERR', null];
        }
        return ['SUCCESS', result];
    }
    public async certificate(user: UserEntity): Promise<string> {
        let payload = {
            username: user.username,
            nickname: user.nickname,
            expired: new Date().getTime() + 24 * 60 * 60 * 1000
        }
        let token = this.jwtService.sign(payload);
        return token;
    }
}